package com.uduemc.biso.node.web.api.service.impl;

import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.util.List;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.mock.web.MockMultipartFile;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;

import com.fasterxml.jackson.core.JsonParseException;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.JsonMappingException;
import com.uduemc.biso.core.extities.center.Host;
import com.uduemc.biso.core.utils.JsonResult;
import com.uduemc.biso.core.utils.RestResult;
import com.uduemc.biso.node.core.entities.HRepertory;
import com.uduemc.biso.node.core.entities.HRepertoryLabel;
import com.uduemc.biso.node.core.feign.HRepertoryLabelFeign;
import com.uduemc.biso.node.core.feign.UploadFeign;
import com.uduemc.biso.node.core.property.GlobalProperties;
import com.uduemc.biso.node.core.utils.RestResultUtil;
import com.uduemc.biso.node.web.api.component.RequestHolder;
import com.uduemc.biso.node.web.api.exception.HostSetuptException;
import com.uduemc.biso.node.web.api.service.HostSetupService;
import com.uduemc.biso.node.web.api.service.UploadService;
import com.uduemc.biso.node.web.api.service.hostsetup.HSFuncService;
import com.uduemc.biso.node.web.api.service.hostsetup.HSUploadSizeService;

import cn.hutool.core.io.FileUtil;
import cn.hutool.core.util.StrUtil;

@Service
public class UploadServiceImpl implements UploadService {

//	private final Logger logger = LoggerFactory.getLogger(getClass());

	@Autowired
	private GlobalProperties globalProperties;

	@Autowired
	private HostSetupService hostSetupServiceImpl;

	@Autowired
	private HSFuncService hSFuncServiceImpl;

	@Autowired
	private HSUploadSizeService hSUploadSizeServiceImpl;

	@Autowired
	private RequestHolder requestHolder;

	@Autowired
	private HRepertoryLabelFeign hRepertoryLabelFeign;

	@Autowired
	private UploadFeign uploadFeign;

	@Override
	public JsonResult validSpace(MultipartFile file) {
		long space = hostSetupServiceImpl.getSpace();
		long usedSpace = hostSetupServiceImpl.getUsedSpace();

		if ((usedSpace + file.getSize()) > space) {
			return JsonResult.messageError("空间不足无法上传！");
		}

		return null;
	}

	@Override
	public JsonResult validFile(MultipartFile file) throws HostSetuptException {
		List<String> allowExt = globalProperties.getUpload().getAllowExt();
		String originalFilename = file.getOriginalFilename();
		String ext = originalFilename.substring(originalFilename.lastIndexOf(".") + 1, originalFilename.length());
		if (!allowExt.contains(ext.toLowerCase())) {
			return JsonResult.messageError("该类型文件不能上传！");
		}
		if(StrUtil.contains(originalFilename, "#")) {
			return JsonResult.messageError("该文件名不能存在 # 特殊字符！");
		}
		short hRepertoryType = globalProperties.getUpload().getHRepertoryType(ext);
		if (hRepertoryType == (short) 5) {
			// 判断是否拥有本地视频组件的功能
			if (!hSFuncServiceImpl.videoFunc()) {
				return JsonResult.messageError("不允许上传，请购买本地视频增值服务！");
			}
		}

		long size = file.getSize();
		long uploadSize = hSUploadSizeServiceImpl.uploadSize(ext.toLowerCase());
		if (uploadSize < 1 || uploadSize < size) {
			return JsonResult.messageError(hSUploadSizeServiceImpl.msgErrSize(ext.toLowerCase()));
		}

		// 获取空间大小判断是否超过了总大小
		if (hostSetupServiceImpl.getUsedSpace() > hostSetupServiceImpl.getSpace()) {
			return JsonResult.messageError("空间不足无法上传！");
		}

		return null;
	}

	@Override
	public boolean validLabelId(long labelId) throws JsonParseException, JsonMappingException, JsonProcessingException, IOException {
		if (labelId == 0) {
			return true;
		}
		long hostId = requestHolder.getHost().getId().longValue();
		RestResult restResult = hRepertoryLabelFeign.findByIdHostId(labelId, hostId);
		HRepertoryLabel data = RestResultUtil.data(restResult, HRepertoryLabel.class);
		if (data == null) {
			return false;
		}
		return true;
	}

	@Override
	public HRepertory nodeUploadHandler(MultipartFile file, long labelId)
			throws JsonParseException, JsonMappingException, JsonProcessingException, IOException {
		RestResult restResult = uploadFeign.handleFileUpload(file, requestHolder.getHost().getId(), labelId, globalProperties.getSite().getBasePath());
		HRepertory data = RestResultUtil.data(restResult, HRepertory.class);
		return data;
	}

	@Override
	public HRepertory nodeLocalUploadHandler(String repertoryPath) throws JsonParseException, JsonMappingException, JsonProcessingException, IOException {
		Host host = requestHolder.getHost();
		return nodeLocalUploadHandler(host, 0L, repertoryPath);
	}

	@Override
	public HRepertory nodeLocalUploadHandler(Host host, long labelId, String repertoryPath)
			throws JsonParseException, JsonMappingException, JsonProcessingException, IOException {
		return nodeLocalUploadHandler(host, labelId, repertoryPath, globalProperties.getSite().getBasePath());
	}

	@Override
	public HRepertory nodeLocalUploadHandler(Host host, long labelId, String repertoryPath, String basePath)
			throws JsonParseException, JsonMappingException, JsonProcessingException, IOException {
		if (!FileUtil.isFile(repertoryPath)) {
			return null;
		}
		File file = new File(repertoryPath);
		MultipartFile multipartFile = new MockMultipartFile("file", file.getName(), null, new FileInputStream(file));

		RestResult restResult = uploadFeign.handleFileUpload(multipartFile, host.getId(), labelId, basePath);
		HRepertory data = RestResultUtil.data(restResult, HRepertory.class);
		return data;
	}

}
